package org.epam.szhuk.overlay;

import org.epam.szhuk.greenway.R;
import org.epam.szhuk.greenway.model.StoredGeoPoint;

import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Matrix;
import android.graphics.Point;

import com.google.android.maps.GeoPoint;
import com.google.android.maps.MapView;
import com.google.android.maps.Overlay;
import com.google.android.maps.Projection;

/**	 
 * Draws cursor image turned from gP0 to gP1.
 * If gP1==null - default rotation
 * gP0 can't be null
 * 
 * mapView.invalidate() have to be called after it
 * 
 * @author Sergii Zhuk
 *
 */
public class PointerOverlay extends Overlay {
	private static final String TAG="PointerOverlay";
	public static final int MIN_RADIUS_NO_POINTER=8; //lat/lon E6-formatted val to mark two pointers by non-rotated circle
	Projection projection;
	StoredGeoPoint storedgP0=null;
	StoredGeoPoint storedgP1=null;
	Context context;
	
	/**
	 * Draws cursor image turned from gP0 to gP1.
	 * If gP1==null - default rotation
	 * gP0 can't be null
	 * 
	 * 
	 * @param projection
	 * @param context
	 * @param gP0
	 * @param gP1
	 */
	public PointerOverlay(Projection projection, Context context, StoredGeoPoint storedgP0, StoredGeoPoint storedgP1) {
		this.projection=projection;
		this.storedgP0=storedgP0;
		this.storedgP1=storedgP1;
		this.context=context;
	}
	@Override
	public void draw(Canvas canvas, MapView mapv, boolean shadow) {
		super.draw(canvas, mapv, shadow);
		GeoPoint gP0=new GeoPoint(storedgP0.getLat(),storedgP0.getLon());
		GeoPoint gP1=null;
		if(storedgP1!=null){
			gP1=new GeoPoint(storedgP1.getLat(),storedgP1.getLon());
		}
		Point screenPoint = new Point();
		projection.toPixels(gP0, screenPoint);
		
		if(storedgP0.getPointType()==StoredGeoPoint.POINT_TYPE_EMPTY){
			Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.map_circle_erase);
			int posX=screenPoint.x-bitmap.getWidth()/2;
			int posY=screenPoint.y-bitmap.getHeight()/2;
			canvas.drawBitmap(bitmap, posX, posY, null); //Setting the image  location on the screen (x,y).
		}
		else{		
			if(gP1==null){ //draw without rotation - circle
				Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.map_circle_red);
				int posX=screenPoint.x-bitmap.getWidth()/2;
				int posY=screenPoint.y-bitmap.getHeight()/2;
				canvas.drawBitmap(bitmap, posX, posY, null); //Setting the image  location on the screen (x,y).
			}
			else if(isClosePoints(gP0,gP1)){ //draw without rotation - circle - because close points
				Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.map_circle_red);
				int posX=screenPoint.x-bitmap.getWidth()/2;
				int posY=screenPoint.y-bitmap.getHeight()/2;
				canvas.drawBitmap(bitmap, posX, posY, null); //Setting the image  location on the screen (x,y).
			}
			else { //draw rotated cursor
				Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.map_arrow_red);
				Matrix matrix = new Matrix();
				float angle=getAngle(gP0,gP1);
				matrix.postRotate(angle);
				Bitmap rotatedBitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);		
				int posX=screenPoint.x-rotatedBitmap.getWidth()/2;
				int posY=screenPoint.y-rotatedBitmap.getHeight()/2;
				canvas.drawBitmap(rotatedBitmap, posX, posY, null); //Setting the image  location on the screen (x,y).
			}	
		}
	}
	
	private static float getAngle(GeoPoint gpFrom, GeoPoint gpTo){
//		if (gpFrom.getLongitudeE6()==gpTo.getLongitudeE6())//x1==x2
//			return 90f;
//		if(gpFrom.getLatitudeE6()==gpTo.getLatitudeE6())//y1==y2
//			return 0f;
		double radValue2= Math.atan2((gpTo.getLongitudeE6()-gpFrom.getLongitudeE6()),(gpTo.getLatitudeE6()-gpFrom.getLatitudeE6()));
		float degValue2= (float)((Math.toDegrees(radValue2)));
		return degValue2; 
	}
	
	private static final boolean isClosePoints(GeoPoint sGp1, GeoPoint sGp2 ){
		int dX=Math.abs(sGp1.getLatitudeE6()-sGp2.getLatitudeE6());
		int dY=Math.abs(sGp1.getLongitudeE6()-sGp2.getLongitudeE6());
		if((dX<MIN_RADIUS_NO_POINTER)||(dY<MIN_RADIUS_NO_POINTER)){
			return true;
		}
		else{
			return false;
		}
	}
} 